package com.baijiayun.liveuibase.devicetesting.fragment

import android.animation.ValueAnimator
import android.content.Context
import android.media.AudioManager
import android.media.SoundPool
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.fragment.app.Fragment
import androidx.lifecycle.ViewModelProvider
import com.baijiayun.livecore.utils.LPRxUtils
import com.baijiayun.liveuibase.R
import com.baijiayun.liveuibase.devicetesting.DeviceTestingViewModel
import io.reactivex.Observable
import io.reactivex.android.schedulers.AndroidSchedulers
import io.reactivex.disposables.Disposable
import kotlinx.android.synthetic.main.bjy_base_fragment_device_testing_speaker.*
import java.util.concurrent.TimeUnit

class DeviceTestingSpeakerFragment : Fragment() {
    private var disposableOfTime: Disposable? = null
    private lateinit var viewModel : DeviceTestingViewModel
    private var soundPool: SoundPool? = null
    private var soundId = 0
    private var volumeCurrent = 1f
    private var isPlaying = false
    private var isPause = false
    private var isFirstPlay = true
    private var valueAnimator: ValueAnimator? = null

    override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
        return inflater.inflate(R.layout.bjy_base_fragment_device_testing_speaker, container, false)
    }

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)
        viewModel = ViewModelProvider(requireActivity()).get(DeviceTestingViewModel::class.java)
        initView()
        initAction()
    }

    private fun initView() {
        bjy_base_fragment_device_testing_speaker_description_tv.visibility = View.GONE
        bjy_base_fragment_device_testing_speaker_positive_btn.visibility = View.GONE
        bjy_base_fragment_device_testing_speaker_negative_btn.visibility = View.GONE
        bjy_base_fragment_device_testing_speaker_positive_btn.setOnClickListener {
            viewModel.speakerResult = true
            viewModel.setTestStep(DeviceTestingViewModel.TestStep.TestMic)
        }
        bjy_base_fragment_device_testing_speaker_negative_btn.setOnClickListener {
            val dialogFragment = DeviceTestingDialogFragment()
            dialogFragment.setTitle(getString(R.string.bjy_base_device_testing_speaker_no_as_question))
            dialogFragment.setContent(getString(R.string.bjy_base_device_testing_speaker_confirm_question))
            dialogFragment.setNegativeButtonText(getString(R.string.bjy_base_device_testing_speaker_no))
            dialogFragment.setPositiveButtonText(getString(R.string.bjy_base_device_testing_speaker_yes))
            dialogFragment.setButtonClickedListener(object : DeviceTestingDialogFragment.OnButtonClickedListener {
                override fun onPositive() {
                    dialogFragment.dismissAllowingStateLoss()
                    viewModel.speakerResult = true
                    viewModel.setTestStep(DeviceTestingViewModel.TestStep.TestMic)
                }

                override fun onNegative() {
                    dialogFragment.dismissAllowingStateLoss()
                    viewModel.speakerResult = false
                    viewModel.setTestStep(DeviceTestingViewModel.TestStep.TestMic)
                }
            })
            dialogFragment.show(activity!!.supportFragmentManager, "speaker")
        }
        bjy_base_fragment_device_testing_play_iv.setOnClickListener {
            if (isFirstPlay || viewModel.isRepeatCheck) {
                isFirstPlay = false
                LPRxUtils.dispose(disposableOfTime)
                disposableOfTime = Observable.timer(2, TimeUnit.SECONDS)
                        .observeOn(AndroidSchedulers.mainThread())
                        .subscribe{
                            bjy_base_fragment_device_testing_speaker_description_tv.visibility = View.VISIBLE
                            bjy_base_fragment_device_testing_speaker_positive_btn.visibility = View.VISIBLE
                            bjy_base_fragment_device_testing_speaker_negative_btn.visibility = View.VISIBLE
                        }
            }
            if (isPlaying && isPause) {
                resumeAudio()
            } else if (isPlaying) {
                pauseAudio()
            } else {
                playAudio()
            }
        }
    }

    private fun initAction() {
        viewModel.earphoneState.observe(this, {
            bjy_base_fragment_device_testing_speaker_name_tv.text = if (it) getString(R.string.bjy_base_device_testing_speaker_other) else getString(R.string.bjy_base_device_testing_speaker_default)
        })
    }

    private fun playAudio() {
        releaseAnimator()
        releaseAudio()
        val am = context!!.getSystemService(Context.AUDIO_SERVICE) as AudioManager
        volumeCurrent = am.getStreamVolume(AudioManager.STREAM_MUSIC).toFloat()
        soundPool = SoundPool(1, AudioManager.STREAM_MUSIC, 0)
        soundId = soundPool!!.load(context, R.raw.speaker, 1)
        // soundId for reuse later on
        soundPool!!.setOnLoadCompleteListener {
            soundPool: SoundPool, sampleId: Int, status: Int -> soundPool.play(soundId, volumeCurrent, volumeCurrent, 0, 0, 1f)
        }
        isPlaying = true
        bjy_base_fragment_device_testing_play_iv.setImageResource(R.drawable.bjy_base_device_testing_icon_pause_normal)
        bjy_base_fragment_device_testing_play_description.text = getText(R.string.bjy_base_device_testing_speaker_is_playing)
        bjy_base_fragment_device_testing_play_click_iv.setImageResource(R.drawable.bjy_base_device_testing_icon_audio)
        valueAnimator = ValueAnimator.ofInt(0, 100)
        valueAnimator?.duration = 9000
        valueAnimator?.addUpdateListener {
            bjy_base_fragment_device_testing_sound_progress.progress = it.animatedValue as Int
            if (it.animatedValue as Int == 100) {
                bjy_base_fragment_device_testing_sound_progress.progress = 0
                bjy_base_fragment_device_testing_play_iv.setImageResource(R.drawable.bjy_base_device_testing_icon_play_normal)
                bjy_base_fragment_device_testing_play_click_iv.setImageResource(R.drawable.bjy_base_device_testing_icon_click)
                bjy_base_fragment_device_testing_play_description.text = getText(R.string.bjy_base_device_testing_speaker_play_tip)
                releaseAnimator()
                releaseAudio()
            }
        }
        valueAnimator?.start()
    }

    private fun pauseAudio() {
        if (soundPool != null) {
            soundPool!!.pause(soundId)
            bjy_base_fragment_device_testing_play_iv.setImageResource(R.drawable.bjy_base_device_testing_icon_play_normal)
            bjy_base_fragment_device_testing_play_click_iv.setImageResource(R.drawable.bjy_base_device_testing_icon_click)
            bjy_base_fragment_device_testing_play_description.text = getText(R.string.bjy_base_device_testing_speaker_play_tip)
            valueAnimator?.pause()
            isPause = true
        }
    }

    private fun resumeAudio() {
        if (soundPool != null) {
            soundPool!!.resume(soundId)
            bjy_base_fragment_device_testing_play_iv.setImageResource(R.drawable.bjy_base_device_testing_icon_pause_normal)
            bjy_base_fragment_device_testing_play_click_iv.setImageResource(R.drawable.bjy_base_device_testing_icon_audio)
            bjy_base_fragment_device_testing_play_description.text = getText(R.string.bjy_base_device_testing_speaker_is_playing)
            valueAnimator?.resume()
            isPause = false
        }
    }

    private fun releaseAudio() {
        if (soundPool != null) {
            if (soundId != 0) {
                soundPool!!.unload(soundId)
            }
            soundPool!!.release()
            soundPool = null
            isPause = false
            isPlaying = false
        }
    }

    private fun releaseAnimator() {
        valueAnimator?.cancel()
        valueAnimator = null
    }

    override fun onPause() {
        super.onPause()
        releaseAudio()
        releaseAnimator()
        LPRxUtils.dispose(disposableOfTime)
    }
}